package com.xiangshizhineng.tianzhangzhi.app.controller;


import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.xiangshizhineng.tianzhangzhi.app.common.R;
import com.xiangshizhineng.tianzhangzhi.app.common.ResultCode;
import com.xiangshizhineng.tianzhangzhi.app.common.base.BaseController;
import com.xiangshizhineng.tianzhangzhi.app.common.exception.ServiceException;
import com.xiangshizhineng.tianzhangzhi.app.filter.AppToken;
import com.xiangshizhineng.tianzhangzhi.app.model.entity.User;
import com.xiangshizhineng.tianzhangzhi.app.model.request.LoginRequest;
import com.xiangshizhineng.tianzhangzhi.app.model.request.LogoutRequest;
import com.xiangshizhineng.tianzhangzhi.app.model.response.DistrictResponse;
import com.xiangshizhineng.tianzhangzhi.app.model.response.LoginResponse;
import com.xiangshizhineng.tianzhangzhi.app.model.response.NoticeResponse;
import com.xiangshizhineng.tianzhangzhi.app.model.response.UserResponse;
import com.xiangshizhineng.tianzhangzhi.app.service.*;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.bind.annotation.*;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.util.*;
import java.util.stream.Collectors;
import java.util.stream.Stream;

import static com.xiangshizhineng.tianzhangzhi.app.utils.ConstantUtils.*;


/**
 * @author
 * @Desc
 * @date
 */
@RestController
@RequestMapping("/user")
@Slf4j
@Api(tags="用户管理")
public class UserController extends BaseController<User> {
    @Autowired
    private UserService userService;
    @Autowired
    private NoticeService noticeService;
    @Autowired
    private DistrictService districtService;

    @ApiOperation(value = "通过id查询", notes = "通过id查询")
    @ApiImplicitParam(name = "id", value = "用户id", dataType = "Long", paramType = "query", required = true)
    @GetMapping(name="详情")
    @AppToken
    public R<UserResponse> view(@RequestParam("id") Long id) {
        Map<String,Object> map = new HashMap(2);
        UserResponse userResponse = userService.findUserById(id);
//        UserResponse userResponse = userService.getById(id);
        /*行政区代码*/
        String xzqdm = userResponse.getXzqdm();
        /*上级田长行政区代码*/
        String code = userResponse.getDistrictResponse().getCode();
        DistrictResponse districtResponse = districtService.getOne(new QueryWrapper<DistrictResponse>().select("level","id").eq("code",xzqdm));
        String level = districtResponse.getLevel();
        if (TZJB_1.equals(userResponse.getTzjb())){
            /*一级田长对应城阳区，没有街道和社区数据，所以将位置信息转成空*/
            userResponse.getDistrictResponse().setName(null);
            map.put("userResponse",userResponse);
            map.put("superior",new ArrayList<>());
            map.put("tzType","0");
            return R.success(map);
        }else if (TZJB_2.equals(userResponse.getTzjb())||TZJB_2.equals(level)){
            /*二级田长可以检索出来街道，但此时街道字段对应的社区，需要重新set*/
            userResponse.getDistrictResponse().setName1(userResponse.getDistrictResponse().getName());
            userResponse.getDistrictResponse().setName(null);
            int res = userService.count(new QueryWrapper<UserResponse>().eq("id",id).like("tzxm","田长制办公室"));
            if(res>0){
                map.put("tzType","1");
            }else{
                map.put("tzType","0");
            }
            map.put("userResponse",userResponse);
            map.put("superior",new ArrayList<>());
            return R.success(map);
        }else if (TZJB_3.equals(userResponse.getTzjb())){
//            List<UserResponse> superior2 = userService.list(new QueryWrapper<UserResponse>()
//                    .lambda()
//                    .eq(StringUtils.isNotEmpty(code),UserResponse::getXzqdm,code)
//                    .eq(UserResponse::getTzjb,TZJB_2)
//            );
            map.put("userResponse",userResponse);
//            map.put("superior",superior2);
            map.put("superior",new ArrayList<>());
            map.put("tzType","0");
            return R.success(map);
        }else if (TZJB_4.equals(userResponse.getTzjb())){
            List<UserResponse> superior3 = userService.list(new QueryWrapper<UserResponse>()
                    .lambda()
                    .eq(StringUtils.isNotEmpty(xzqdm),UserResponse::getXzqdm,xzqdm)
                    .eq(UserResponse::getTzjb,TZJB_3));
            /*List<UserResponse> superior2 = userService.list(new QueryWrapper<UserResponse>()
                    .lambda()
                    .eq(StringUtils.isNotEmpty(code),UserResponse::getXzqdm,code)
                    .eq(UserResponse::getTzjb,TZJB_2));*/
            List<UserResponse> superior2 = new ArrayList<>();
            /*合并*/
            List<UserResponse> res = Stream.of(superior3, superior2).flatMap(Collection::stream).collect(Collectors.toList());
            /*根据田长级别排序*/
            List<UserResponse> newList = res.stream().sorted(Comparator.comparing(UserResponse::getTzjb)).collect(Collectors.toList());
            map.put("userResponse",userResponse);
            map.put("superior",newList);
            map.put("tzType","0");
            return R.success(map);
        }else {
            return R.fail(ResultCode.ERROR.getCode(),"用户职位不存在");
        }
    }

    @ApiOperation(value = "我的模块下的通知公告", notes = "查询所有公告")
    @ApiImplicitParams({
            @ApiImplicitParam(name = "s", value = "每页的条数", paramType = "query"),
            @ApiImplicitParam(name = "p", value = "请求的页码", paramType = "query"),
            @ApiImplicitParam(name = "createTime", value = "排序字段，true升序(asc),false降序(desc),默认降序显示最紧急的公告",dataType = "Boolean", paramType = "query"),
            @ApiImplicitParam(name = "noticeStatus", value = "排序字段，true升序(asc),false降序(desc),默认降序显示最新的消息",dataType = "Boolean", paramType = "query"),
            @ApiImplicitParam(name = "title", value = "根据通知名称模糊查询", dataType = "String", paramType = "query")
    })
    @GetMapping("/notice")
    @Transactional(rollbackFor = Exception.class)
    @AppToken
    public R<NoticeResponse> noticeSelect(@RequestParam(value = "s",required = false,defaultValue = "20")Long s,
                                          @RequestParam(value = "p",required = false,defaultValue = "1")Long p,
                                          @RequestParam(value = "noticeStatus",required = false)Boolean noticeStatus,
                                          @RequestParam(value = "createTime",required = false)Boolean createTime,
                                          @RequestParam(value = "title",required = false)String title) {
        Page<NoticeResponse> page = new Page<>(p,s);
        Page<NoticeResponse> d = noticeService.page(page,new QueryWrapper<NoticeResponse>()
                .lambda()
                .le(NoticeResponse::getStartDate,new Date())
                .ge(NoticeResponse::getEndDate,new Date())
                .like(StringUtils.isNotEmpty(title),NoticeResponse::getTitle,title)
                                                        /*避免空指针，为null排序也不会生效*/
                .orderBy(noticeStatus!=null?true:false,noticeStatus!=null?noticeStatus:false,NoticeResponse::getNoticeStatus)
                .orderBy(true,createTime!=null?createTime:false,NoticeResponse::getCreateTime)
        );
        return R.success(d);
    }

    @ApiOperation(value = "通知公告详情", notes = "点击列表进入具体公告详情")
    @ApiImplicitParam(name = "id", value = "公告id", dataType = "Long", paramType = "query", required = true)
    @GetMapping("/noticeDetails")
    @AppToken
    public R<NoticeResponse> noticeDetails(Long id){
        NoticeResponse noticeResponse = noticeService.getById(id);
        return R.success(noticeResponse);
    }


    @PostMapping("/login")
    @ApiOperation(value = "登录", notes = "登录")
    @ApiImplicitParam(name = "loginRequest", value = "LoginRequest实体类", paramType = "body", required = true)
    public R<LoginResponse> login(@RequestBody LoginRequest loginRequest, HttpServletRequest request, HttpServletResponse response) throws IOException {
        log.info("user login, user_name: {}" + loginRequest.getUserName());
        LoginResponse loginResponse = userService.login(loginRequest, request,response);
        if (loginResponse!=null){
            return R.success(loginResponse);
        }
        return R.fail("100400","用户名或密码错误");
    }


    @PostMapping("/logout")
    @ApiOperation(value = "退出登录", notes = "退出登录")
    @AppToken
    public R logout(@RequestBody LogoutRequest logoutRequest, HttpServletRequest request) {
        String userName = logoutRequest.getUserName();
        if (userName == null) {
            throw new ServiceException("用户名不能为空");
        }
        log.info("user logout, user_name: {}", userName);
        userService.logout(userName, request);
        return R.success();
    }
}
